home *** CD-ROM | disk | FTP | other *** search
/ Personal Computer World 2009 February / PCWFEB09.iso / Software / Linux / Kubuntu 8.10 / kubuntu-8.10-desktop-i386.iso / casper / filesystem.squashfs / usr / bin / ucf < prev    next >
Text File  |  2008-09-03  |  33KB  |  984 lines

  1. #!/bin/bash
  2. #                               -*- Mode: Sh -*-
  3. # updateConfFile.sh ---
  4. # Author           : Manoj Srivastava ( srivasta@glaurung.green-gryphon.com )
  5. # Created On       : Fri Feb  1 03:41:47 2002
  6. # Created On Node  : glaurung.green-gryphon.com
  7. # Last Modified By : Manoj Srivastava
  8. # Last Modified On : Tue Jun  6 09:48:22 2006
  9. # Last Machine Used: glaurung.internal.golden-gryphon.com
  10. # Update Count     : 186
  11. # Status           : Unknown, Use with caution!
  12. # HISTORY          :
  13. # Description      :
  14. #
  15. # This script attempts to provide conffile like handling for files not
  16. # shipped in a Debian package, but handled by the postinst. Using this
  17. # script, one may ship a bunch of default cofiguration files somewhere
  18. # in /usr (/usr/share/<pkg> is a good location), and maintain files in
  19. # /etc.
  20. #
  21. # The motivation for this script was to provide conffile like handling
  22. # for start files for emacs lisp packages (for example,
  23. # /etc/emacs21/site-stard.d/50psgml-init.el) These start files are not
  24. # shipped with the package, instead, they are installed during the
  25. # post installation configuration phase by the script
  26. # /usr/lib/emacsen-common/emacs-package-install $package_name.
  27. #
  28. # This script is meant to be invoked by the packages install script at
  29. # /usr/lib/emacsen-common/packages/install/$package_name for each
  30. # flavour of installed emacsen by calling it with the proper values of
  31. # new file (/usr/share/emacs/site-lisp/<pkg>/<pkg>-init.el), and dest file
  32. # (/etc/emacs21/site-stard.d/50<pkg>-init.el)), and it should do the rest.
  33. #
  34.  
  35. # make sure we exit on error
  36. set -e
  37.  
  38. # set the version and revision
  39. progname="`basename \"$0\"`"
  40. pversion='$Revision: 1.26 $'
  41.  
  42. ######################################################################
  43. ########                                                     #########
  44. ########              Utility functions                      #########
  45. ########                                                     #########
  46. ######################################################################
  47. setq() {
  48.     # Variable Value Doc_string
  49.     if [ "x$2" = "x" ]; then
  50.     echo >&2 "$progname: Unable to determine $3"
  51.     exit 1;
  52.     else
  53.     if [ "x$VERBOSE" != "x" ]; then
  54.         echo >&2 "$progname: $3 is $2";
  55.     fi
  56.     eval "$1=\"\$2\"";
  57.     fi
  58. }
  59.  
  60. # Use debconf to show the differences
  61. show_diff() {
  62.     if [ -z "$1" ]; then
  63.     DIFF="There are no non-white space differences in the files."
  64.     else
  65.         if  [ 99999 -lt $(echo $1 | wc -c | awk '{print $1; }') ]; then
  66.             DIFF="The differences between the files are too large to display."
  67.         else
  68.             DIFF="$1"
  69.         fi
  70.     fi
  71.     if [ "$DEBCONF_OK" = "YES" ] && [ "$DEBIAN_HAS_FRONTEND" ]; then
  72.     templ=ucf/show_diff
  73.     db_capb escape
  74.     db_reset $templ
  75.     db_subst $templ DIFF "$(printf %s "$DIFF" | debconf-escape -e)"
  76.     db_input critical $templ || true
  77.     db_go
  78.     db_get $templ
  79.     db_capb
  80.     else
  81.     echo "$DIFF" | sensible-pager
  82.     fi
  83. }
  84.  
  85. withecho () {
  86.         echo " $@" >&2
  87.         "$@"
  88. }
  89.  
  90. usageversion () {
  91.         cat >&2 <<END
  92. Debian GNU/Linux $progname $pversion.
  93.            Copyright (C) 2002-2005 Manoj Srivastava.
  94. This is free software; see the GNU General Public Licence for copying
  95. conditions.  There is NO warranty.
  96.  
  97. Usage: $progname  [options] new_file  destination
  98. Options:
  99.      -h,     --help          print this message
  100.      -s foo, --src-dir  foo  Set the src dir (historical md5sums live here)
  101.              --sum-file bar  Force the historical md5sums to be read from
  102.                              this file.  Overrides any setting of --src-dir.
  103.      -d [n], --debug    [n]  Set the Debug level to N
  104.      -n,     --no-action     Dry run. No action is actually taken.
  105.      -v,     --verbose       Make the script verbose
  106.              --three-way     Register this file in the cache, and turn on the
  107.                              diff3 option allowing the merging of maintainer
  108.                              changes into a (potentially modified) local 
  109.                              configuration file. )
  110.              --state-dir bar Set the state directory to bar instead of the
  111.                              default '/var/lib/ucf'. Used mostly for testing.
  112.              --debconf-ok    Indicate that it is ok for uct to use an already
  113.                              running debconf instance for prompting.
  114.              --debconf-template bar
  115.                              Specify an alternate, caller-provided debconf
  116.                              template to use for prompting.
  117. Usage: $progname  -p  destination
  118.      -p,     --purge         Remove any reference to destination from records
  119.  
  120. By default, the directory the new_file lives in is assumed to be the src-dir,
  121. which is where we look for any historical md5sums.
  122.  
  123. END
  124.     
  125. }
  126.  
  127. ######################################################################
  128. ########                                                     #########
  129. ########                  DebConf stuff                      #########
  130. ########                                                     #########
  131. ######################################################################
  132.  
  133. # Is debconf already running? Kinda tricky, because it will be after the
  134. # confmodule is sourced, so only test before that.
  135. if [ -z "$DEBCONF_ALREADY_RUNNING" ]; then
  136.     if [ "$DEBIAN_HAS_FRONTEND" ]; then
  137.     DEBCONF_ALREADY_RUNNING='YES'
  138.     else
  139.     DEBCONF_ALREADY_RUNNING='NO'
  140.     fi
  141. fi
  142.  
  143. export DEBCONF_ALREADY_RUNNING
  144.  
  145. # Start up debconf or at least get the db_* commands available.
  146. if [ -e /usr/share/debconf/confmodule ]; then
  147.     if test $(id -u) = 0; then
  148.     . /usr/share/debconf/confmodule
  149.  
  150.     # Load our templates, just in case our template has
  151.     # not been loaded or the Debconf DB lost or corrupted
  152.     # since then.
  153.     db_x_loadtemplatefile /var/lib/dpkg/info/ucf.templates ucf
  154.     else
  155.         echo >&2 "$progname: Not loading confmodule, since we are not running as root."
  156.     fi
  157.     # Only set the title if debconf was not already running.
  158.     # If it was running, then we do not want to clobber the
  159.     # title used for configuring the whole package with debconf.
  160.     if [ "$DEBCONF_ALREADY_RUNNING" = 'NO' ]; then
  161.     if ! db_settitle ucf/title 2>/dev/null; then
  162.               # Older debconf that does not support that command.
  163.             if test $(id -u) = 0; then
  164.         db_title "Modified configuration file"
  165.             else
  166.                 echo >&2 "$progname: Not changing title, since we are not running as root."
  167.             fi
  168.     fi
  169.     fi
  170. fi
  171.     
  172.  
  173. if [ -z "$DEBCONF_OK" ]; then
  174.     if [ "$DEBCONF_ALREADY_RUNNING" = 'YES' ]; then
  175.     DEBCONF_OK='NO'
  176.     else
  177.     DEBCONF_OK='YES'
  178.     fi
  179. fi
  180.  
  181. if [ "$DEBCONF_ALREADY_RUNNING" ] && [ "$DEBCONF_OK" = NO ]; then
  182.     # Commented out for now, uncomment after a while to begin nagging
  183.     # maintainers to fix their scripts.
  184.     #cat \
  185. <<END
  186. *** WARNING: ucf was run from a maintainer script that uses debconf, but
  187.              the script did not pass --debconf-ok to ucf. The maintainer
  188.              script should be fixed to not stop debconf before calling ucf,
  189.              and pass it this parameter. For now, ucf will revert to using
  190.              old-style, non-debconf prompting. Ugh!
  191.  
  192.              Please inform the package maintainer about this problem.
  193. END
  194. fi
  195.  
  196.  
  197. purge_md5sum () {
  198.     for i in $(/usr/bin/seq 6 -1 0); do
  199.     if [ -e "${statedir}/hashfile.${i}" ]; then
  200.         if [ "X$docmd" = "XYES" ]; then
  201.         cp -pf "${statedir}/hashfile.${i}" \
  202.             "${statedir}/hashfile.$(($i+1))"
  203.         else 
  204.         echo cp -pf "${statedir}/hashfile.${i}" \
  205.                           "${statedir}/hashfile.$(($i+1))"
  206.         fi 
  207.     fi 
  208.     done
  209.     if [ -e "$statedir/hashfile" ]; then
  210.     if [ "X$docmd" = "XYES" ]; then
  211.         cp -pf "$statedir/hashfile"  "$statedir/hashfile.0" 
  212.     else
  213.         echo cp -pf "$statedir/hashfile"  "$statedir/hashfile.0" 
  214.     fi
  215.     if [ "X$docmd" = "XYES" ]; then
  216.         set +e
  217.         if [ "X$VERBOSE" != "X" ]; then
  218.         echo "egrep -v [[:space:]]${safe_dest_file}$ $statedir/hashfile"
  219.         egrep -v "[[:space:]]${safe_dest_file}$"  "$statedir/hashfile" \
  220.             || true;
  221.         fi
  222.         #echo "egrep -v [[:space:]]${safe_dest_file}$ $statedir/hashfile"
  223.         egrep -v "[[:space:]]${safe_dest_file}$" "$statedir/hashfile" > \
  224.         "$statedir/hashfile.tmp" || true; 
  225.         if [ "X$docmd" = "XYES" ]; then
  226.         mv -f "$statedir/hashfile.tmp"  "$statedir/hashfile" 
  227.         else
  228.         echo mv -f "$statedir/hashfile.tmp"  "$statedir/hashfile"
  229.         fi
  230.         set -e
  231.     fi
  232.     fi
  233.     test -n "$VERBOSE" && echo "The cache file is $cached_file"
  234.     if [ ! -z "$cached_file" -a -f "$statedir/cache/$cached_file" ]; then
  235.     $action rm -f "$statedir/cache/$cached_file"
  236.     fi
  237. }
  238.  
  239. replace_md5sum () {
  240.     for i in $(/usr/bin/seq 6 -1 0); do
  241.     if [ -e "${statedir}/hashfile.${i}" ]; then
  242.         if [ "X$docmd" = "XYES" ]; then
  243.         cp -pf "${statedir}/hashfile.${i}" \
  244.             "${statedir}/hashfile.$(($i+1))"
  245.         else
  246.         echo cp -pf "${statedir}/hashfile.${i}" \
  247.             "${statedir}/hashfile.$(($i+1))"
  248.         fi
  249.     fi
  250.     done
  251.     if [ -e "$statedir/hashfile" ]; then
  252.     if [ "X$docmd" = "XYES" ]; then
  253.         cp -pf "$statedir/hashfile"  "$statedir/hashfile.0" 
  254.     else
  255.         echo cp -pf "$statedir/hashfile"  "$statedir/hashfile.0" 
  256.     fi
  257.     if [ "X$docmd" = "XYES" ]; then
  258.         set +e
  259.         if [ "X$VERBOSE" != "X" ]; then
  260.         echo "(egrep -v \"[[:space:]]${safe_dest_file}$\" \"$statedir/hashfile\";"
  261.         egrep -v "[[:space:]]${safe_dest_file}$"  "$statedir/hashfile" || true;
  262.          md5sum "$orig_new_file" | sed "s|$orig_new_file|$dest_file|" ;
  263.         fi
  264.         egrep -v "[[:space:]]${safe_dest_file}$" "$statedir/hashfile" > \
  265.         "$statedir/hashfile.tmp" || true; 
  266.         md5sum "$orig_new_file" | sed "s|$orig_new_file|$dest_file|" >> \
  267.         "$statedir/hashfile.tmp"; 
  268.         mv -f "$statedir/hashfile.tmp"  "$statedir/hashfile" 
  269.         set -e
  270.     else
  271.         echo "(egrep -v \"[[:space:]]${safe_dest_file}$\" \"$statedir/hashfile\""
  272.         echo " md5sum \"$orig_new_file\" | sed \"s|$orig_new_file|$dest_file|\"; " 
  273.         echo ") | sort > \"$statedir/hashfile\""
  274.     fi
  275.     else
  276.     if [ "X$docmd" = "XYES" ]; then
  277.         md5sum "$orig_new_file" | sed "s|$orig_new_file|$dest_file|"  > \
  278.         "$statedir/hashfile" 
  279.     else
  280.         echo " md5sum \"$orig_new_file\" | sed \"s|$orig_new_file|$dest_file|\" >" \
  281.         "\"$statedir/hashfile\""
  282.     fi
  283.     fi
  284.     if [ "X$THREEWAY" != "X" ]; then
  285.     $action cp -pf "$orig_new_file" "$statedir/cache/$cached_file"
  286.     fi
  287.     # cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  288. }
  289.  
  290. replace_conf_file () {
  291.     # do not mangle $dest_file since it's the one registered in the hashfile
  292.     # or we have been ask to register
  293.     real_file="$dest_file"
  294.     if [ -L "$dest_file" ]; then
  295.     real_file="$(readlink -nf $dest_file || :)"
  296.     if [ "x$real_file" = "x" ]; then
  297.         echo >&2 "$dest_file is a broken symlink!"
  298.         $action rm -f "$dest_file";
  299.         real_file="$dest_file"
  300.     fi
  301.     fi
  302.     if [ -e "$real_file" ]; then
  303.     if [ -z "$RETAIN_OLD" ]; then
  304.         #echo "Saving  ${real_file}.${OLD_SUFFIX},  in case."
  305.         if [ "x$VERBOSE" != "x" ]; then
  306.         echo >&2 "Not saving ${real_file}, since it was unmodified"
  307.         fi
  308.     else
  309.         $action cp -pf "${real_file}" "${real_file}.${OLD_SUFFIX}"
  310.     fi
  311.     fi
  312.     $action cp -pf "$new_file" "${real_file}"
  313.     replace_md5sum;
  314. }
  315.  
  316.  
  317. ######################################################################
  318. ########                                                     #########
  319. ########              Command line args                      #########
  320. ########                                                     #########
  321. ######################################################################
  322. #
  323. # Long term variables#
  324. #
  325. docmd='YES'
  326. action='withecho'
  327. action=
  328. DEBUG=0
  329. VERBOSE=''
  330. statedir='/var/lib/ucf';
  331. THREEWAY=
  332.  
  333. DIST_SUFFIX="ucf-dist"
  334. NEW_SUFFIX="ucf-new"
  335. OLD_SUFFIX="ucf-old"
  336.  
  337. # Note that we use `"$@"' to let each command-line parameter expand to a
  338. # separate word. The quotes around `$@' are essential!
  339. # We need TEMP as the `eval set --' would nuke the return value of getopt.
  340. TEMP=`getopt -a -o hs:d::D::nv -n "$progname" \
  341.       --long help,src-dir:,sum-file:,dest-dir:,debug::,DEBUG::,no-action,purge,verbose,three-way,debconf-ok,debconf-template:,state-dir: \
  342.              -- "$@"`
  343.  
  344. if [ $? != 0 ] ; then
  345.     echo "Error handling options.Terminating..." >&2 ;
  346.     exit 1 ;
  347. fi
  348.  
  349. # Note the quotes around `$TEMP': they are essential!
  350. eval set -- "$TEMP"
  351.  
  352. while true ; do
  353.     case "$1" in
  354.     -h|--help) usageversion;                        exit 0 ;;
  355.     -n|--no-action) action='echo'; docmd='NO';      shift  ;;
  356.     -v|--verbose) VERBOSE=1;                        shift  ;;
  357.     -s|--src-dir)
  358.         opt_source_dir="$2";                       shift 2 ;;
  359.     --sum-file)
  360.         opt_old_mdsum_file="$2";          shift 2 ;;
  361.     --state-dir)
  362.         opt_state_dir="$2";                        shift 2 ;;
  363.     --debconf-template)
  364.         override_template="$2";                    shift 2 ;;
  365.     -D|-d|--debug|--DEBUG)
  366.             # d has an optional argument. As we are in quoted mode,
  367.             # an empty parameter will be generated if its optional
  368.             # argument is not found.
  369.         case "$2" in
  370.         "") setq DEBUG 1    "The Debug value"; shift 2 ;;
  371.         *)  setq DEBUG "$2" "The Debug value"; shift 2 ;;
  372.         esac ;;
  373.         -p|--purge) PURGE=YES;                         shift   ;;
  374.        --three-way) THREEWAY=YES;                       shift   ;;
  375.        --debconf-ok) DEBCONF_OK=YES;                    shift   ;;
  376.     --)  shift ;                                   break   ;;
  377.     *) echo >&2 "Internal error!" ; exit 1 ;;
  378.     esac
  379. done
  380. # Need to run as root, or else the 
  381. if test $(id -u) != 0; then
  382.     if [ "$docmd" = "YES" ]; then
  383.         echo "$progname: Need to be run as root." >&2
  384.         echo "$progname: Setting up no action mode." >&2
  385.         action='echo'; docmd='NO'; 
  386.     fi
  387. fi
  388.  
  389. if [ "X$PURGE" = "XYES" ]; then
  390.     if [ $# != 1 ]; then
  391.     echo >&2 "*** ERROR: Need exactly one argument when purging, got $#";
  392.     echo >&2 ""
  393.     usageversion;
  394.     exit 0 ;        
  395.     fi
  396.     temp_dest_file=$1;
  397.     setq dest_file "$(readlink -q -m $temp_dest_file)" "The Destination file";
  398. else
  399.     if [ $# != 2 ]; then
  400.     echo >&2 "*** ERROR: Need exactly two arguments, got $#";
  401.     echo >&2 ""
  402.     usageversion;
  403.     exit 0 ;
  404.     fi
  405.     temp_new_file=$1;
  406.     temp_dest_file=$2;
  407.  
  408.     if [ ! -e "$temp_new_file" ]; then
  409.     echo >&2 "Error: The new file ${temp_new_file} does not exist!";
  410.     exit 1;
  411.     fi
  412.     setq new_file  "$(readlink -q -m $temp_new_file)"  "The new file";
  413.     setq dest_file "$(readlink -q -m $temp_dest_file)" "The Destination file";
  414. fi
  415.  
  416.  
  417. safe_dest_file=$(echo $dest_file | perl -nle 'print "\Q$_\E\n"')
  418.  
  419.  
  420.  
  421. # Load site defaults and over rides.
  422. if [ -f /etc/ucf.conf ]; then
  423.     . /etc/ucf.conf
  424. fi
  425.  
  426. # Command line, env variable, config file, or default
  427. if [ ! "x$opt_source_dir" = "x" ]; then
  428.     setq source_dir "$opt_source_dir" "The Source directory"
  429. elif [ ! "x$UCF_SOURCE_DIR" = "x" ]; then
  430.     setq source_dir "$UCF_SOURCE_DIR" "The Source directory"
  431. elif [ ! "x$conf_source_dir" = "x" ]; then
  432.     setq source_dir "$conf_source_dir" "The Source directory"
  433. else
  434.     if [ "X$new_file" != "X" ]; then
  435.     setq source_dir $(dirname "$new_file") "The Source directory"
  436.     else
  437.     setq source_dir /tmp "The Source directory"
  438.     fi
  439.     
  440. fi
  441.  
  442. if [ "X$PAGER" != "X" ] && type -a -p $PAGER >& /dev/null ; then
  443.     my_pager=$(type -a -p $PAGER);
  444. elif [ -s /usr/bin/pager ] && 
  445.      [ "X$(readlink -e /usr/bin/pager || :)" != "X" ]; then
  446.     my_pager=/usr/bin/pager
  447. elif [ -x /usr/bin/sensible-pager ]; then
  448.     my_pager=/usr/bin/sensible-pager
  449. elif [ -x /bin/more ]; then
  450.     my_pager=/bin/more
  451. else
  452.     my_pager=
  453. fi
  454.  
  455.  
  456.  
  457. if [ "X$my_pager" = "X" ]; then
  458.     STOP=YES
  459. elif [ "X$my_pager" = "X/bin/more" ]; then
  460.     STOP=YES
  461. fi
  462.  
  463. # Command line, env variable, config file, or default
  464. if [ ! "x$opt_state_dir" = "x" ]; then
  465.     setq statedir "$opt_state_dir" "The State directory"
  466. elif [ ! "x$UCF_STATE_DIR" = "x" ]; then
  467.     setq statedir "$UCF_STATE_DIR" "The State directory"
  468. elif [ ! "x$conf_state_dir" = "x" ]; then
  469.     setq statedir "$conf_state_dir" "The State directory"
  470. else
  471.     setq statedir '/var/lib/ucf'  "The State directory"    
  472. fi
  473.  
  474. # Command line, env variable, config file, or default
  475. if [ ! "x$opt_force_conffold" = "x" ]; then
  476.     setq force_conffold "$opt_force_conffold" "Keep the old file"
  477. elif [ ! "x$UCF_FORCE_CONFFOLD" = "x" ]; then
  478.     setq force_conffold "$UCF_FORCE_CONFFOLD" "Keep the old file"
  479. elif [ ! "x$conf_force_conffold" = "x" ]; then
  480.     setq force_conffold "$conf_force_conffold" "Keep the old file"
  481. else
  482.     force_conffold=''
  483. fi
  484.  
  485. # Command line, env variable, config file, or default
  486. if [ ! "x$opt_force_conffnew" = "x" ]; then
  487.     setq force_conffnew "$opt_force_conffnew" "Replace the old file"
  488. elif [ ! "x$UCF_FORCE_CONFFNEW" = "x" ]; then
  489.     setq force_conffnew "$UCF_FORCE_CONFFNEW" "Replace the old file"
  490. elif [ ! "x$conf_force_conffnew" = "x" ]; then
  491.     setq force_conffnew "$conf_force_conffnew" "Replace the old file"
  492. else
  493.     force_conffnew=''
  494. fi
  495.  
  496. # Command line, env variable, config file, or default
  497. if [ ! "x$opt_force_conffmiss" = "x" ]; then
  498.     setq force_conffmiss "$opt_force_conffmiss" "Replace any missing files"
  499. elif [ ! "x$UCF_FORCE_CONFFMISS" = "x" ]; then
  500.     setq force_conffmiss "$UCF_FORCE_CONFFMISS" "Replace any missing files"
  501. elif [ ! "x$conf_force_conffmiss" = "x" ]; then
  502.     setq force_conffmiss "$conf_force_conffmiss" "Replace any missing files"
  503. else
  504.     force_conffmiss=''
  505. fi
  506.  
  507. if [ -n "$opt_old_mdsum_file" ]; then
  508.     setq old_mdsum_file "$opt_old_mdsum_file" "The md5sum is found here"
  509. elif [ ! "x$UCF_OLD_MDSUM_FILE" = "x" ]; then
  510.     setq old_mdsum_file "$UCF_OLD_MDSUM_FILE" "The md5sum is found here"
  511. elif [ ! "x$conf_old_mdsum_file" = "x" ]; then
  512.     setq old_mdsum_file "$conf_old_mdsum_file" "Replace the old file"
  513. else
  514.     old_mdsum_file="$source_dir/"$(basename "${new_file}")".md5sum";
  515. fi
  516.  
  517.  
  518. if [ "X$force_conffold" != "X" -a "X$force_conffnew" != "X" ]; then
  519.     echo >&2 "Error: Only one of force_conffold and force_conffnew should";
  520.     echo >&2 "       be set";
  521.     exit 1;
  522. fi
  523.  
  524. # VERBOSE of 0 is supposed to be the same as not setting VERBOSE
  525. if [ "X$VERBOSE" = "X0" ]; then
  526.     VERBOSE=''
  527. fi
  528.  
  529.  
  530. #
  531. if [ -e "$statedir/hashfile" -a ! -w "$statedir/hashfile" ]; then
  532.     echo >&2 "ucf: do not have write privilege to the state data"
  533.     if [ "X$docmd" = "XYES" ]; then
  534.     exit 1;
  535.     fi
  536. fi
  537.  
  538. if [ ! -d $statedir/cache ]; then
  539.     $action mkdir -p $statedir/cache ;
  540. fi
  541.  
  542. # test and see if this file exists in the database
  543. if [ -e "$statedir/hashfile" ]; then
  544.     if [ "X$VERBOSE" != "X" ]; then
  545.     echo >&2 "The hash file exists"
  546.     echo egrep "[[:space:]]${safe_dest_file}$" "$statedir/hashfile"
  547.     egrep "[[:space:]]${safe_dest_file}$" "$statedir/hashfile" || true
  548.     fi
  549.     lastsum=$(egrep "[[:space:]]${safe_dest_file}$" "$statedir/hashfile" | \
  550.                    awk '{print $1;}' )
  551. fi
  552.  
  553. old_mdsum_dir="$source_dir/"$(basename "${new_file}")".md5sum.d";
  554.  
  555.  
  556. cached_file=$(echo $dest_file | tr / :)
  557. orig_new_file="$new_file"    # Since sometimes we replace the newfile below
  558.  
  559. # Determine the action for the current file. The default is to ask,
  560. # with non-replacement being the norm.
  561. # If the config dir exists
  562. #   if file in always overwrite, state +=1;
  563. #   fi
  564. #   if file in never overwrite, state +=2;
  565. #   fi
  566. #   if file in ask; state +=4
  567. #   fi
  568. #   if state == 0; then state = default
  569. #   if state >= 4; ask
  570. #   if state == 3;  ask
  571. #   if state == 2; exit
  572. #   if state == 1; then replace_conffile; exit
  573.  
  574. if [ $DEBUG -gt 0 ]; then
  575.     cat <<EOF
  576. The new start file is      \`$new_file\'
  577. The destination is         \`$dest_file\' (\`$safe_dest_file\')
  578. The history is kept under  \'$source_dir\'
  579. The file may be cached at \'$statedir/cache/$cached_file\'
  580. EOF
  581.     if [ -s "$dest_file" ]; then
  582.     echo "The destination file exists, and has md5sum:"
  583.     md5sum "$dest_file"
  584.     else
  585.     echo "The destination file does not exist."
  586.     fi
  587.     if [ "X$lastsum" != "X" ]; then
  588.     echo "The old md5sum exists, and is:"
  589.     echo $lastsum
  590.     else 
  591.     echo "The old md5sum does not exist."
  592.         if [ -d "$old_mdsum_dir" -o -f "$old_mdsum_file" ]; then
  593.             echo "However, there are historical md5sums around."
  594.         fi
  595.     fi
  596.     if [ -e "$new_file" ]; then
  597.     echo "The new file exists, and has md5sum:"
  598.     md5sum "$new_file"
  599.     else 
  600.     echo "The new file does not exist."
  601.     fi
  602.     if [ -d "$old_mdsum_dir" ]; then
  603.     echo "The historical md5sum dir $old_mdsum_dir exists"
  604.     elif [ -f "$old_mdsum_file" ]; then
  605.     echo "The historical md5sum file $old_mdsum_file exists"
  606.     else
  607.     echo "Historical md5sums are not available"
  608.     fi
  609. fi
  610.  
  611.  
  612. if [ "X$PURGE" = "XYES" ]; then
  613.     if [ "X$VERBOSE" != "X" ]; then
  614.     echo >&2 "Preparing to purge ${dest_file}"
  615.     fi
  616.     purge_md5sum;
  617.     exit 0;
  618. fi
  619.  
  620. newsum=$(md5sum "$new_file" | awk '{print $1}')
  621.  
  622.  
  623. ######################################################################
  624. ########                                                     #########
  625. ########               Do the replacement                    #########
  626. ########                                                     #########
  627. ######################################################################
  628. # Step 1: If we have no record of this file, and dest file
  629. #         does, We need to determine how to initialize the
  630. #         ${old_mdsum_prefix}.old file..               
  631. if [ -e "$dest_file" ]; then
  632.     destsum=$(md5sum "$dest_file"  | awk '{print $1}');
  633.     if [ "X$lastsum" = "X" ]; then
  634. #      a: If we have a directory containing historical md5sums of this
  635. #         file in question, we should look and see if the currently
  636. #         installed file matches any of the old md5sums; in which case
  637. #         it can be silently replaced.
  638.     if [ -d "$old_mdsum_dir" -o -f "$old_mdsum_file" ]; then
  639.         if [ -d "$old_mdsum_dir"  ]; then
  640.         for file in ${old_mdsum_dir}/*; do
  641.             oldsum=$(cat "$file"  | awk '{print $1}');
  642.             if [ "$oldsum" = "$destsum"  ]; then
  643.             if [ "X$force_conffold" = "X" ]; then
  644. #                           Bingo! replace, set the md5sum, and we are done 
  645.                 if [ "X$VERBOSE" != "X" ]; then
  646.                 echo >&2 \
  647.                     "Replacing config file $dest_file with new version"
  648.                 fi
  649.                 replace_conf_file;
  650.                 exit 0;
  651.             else
  652.                 replace_md5sum;
  653.                 cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  654.                 exit 0;
  655.             fi
  656.             fi
  657.         done
  658.         elif [ -f "$old_mdsum_file" ]; then
  659.         oldsum=$(egrep "^${destsum}" "$old_mdsum_file" || true)
  660.         if [ "X$oldsum" != "X" ]; then
  661. #                    Bingo
  662.             if [ "X$force_conffold" = "X" ]; then
  663.             if [ "X$VERBOSE" != "X" ]; then
  664.                 echo >&2 \
  665.                 "Replacing config file $dest_file with new version"
  666.             fi
  667.             replace_conf_file;
  668.             exit 0;
  669.             else
  670.             replace_md5sum;
  671.             cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  672.             exit 0;
  673.             fi
  674.         fi
  675.         fi
  676. #       Well, nothing matched. We now check to see if the
  677. #       maintainer has an opinion on how to set the ``md5sum of the
  678. #       previously installed version'', since we have no way of
  679. #       determining that automatically. Please note that unless
  680. #       there are limited number of previously released packages
  681. #       (like just one), the maintainer is also making a guess at
  682. #       this point by supplying a historical md5sum default file. 
  683.         if [ "X$VERBOSE" != "X" ]; then
  684.         echo >&2 "Histotical md5sums did not match."
  685.         fi
  686.         if [ -d "$old_mdsum_dir"  ]; then
  687.         if [ -e "${old_mdsum_dir}/default" ]; then
  688.             if [ "X$VERBOSE" != "X" ]; then
  689.             echo >&2 "However, a default entry exists, using it."
  690.             fi
  691.             lastsum=$(cat "${old_mdsum_dir}/default" | \
  692.             awk '{print $1;}')
  693.             do_replace_md5sum=1;
  694.         fi
  695.         elif [ -f "$old_mdsum_file" ]; then
  696.         oldsum=$(egrep "[[:space:]]default$" "$old_mdsum_file" | \
  697.             awk '{print $1;}')
  698.         if [ "X$oldsum" != "X" ]; then
  699. #                    Bingo
  700.             lastsum=$oldsum;
  701.             do_replace_md5sum=1;
  702.         fi
  703.         fi
  704.     fi
  705.  
  706. #       At this point, we are almost certain that either the
  707. #       historical record of md5sums is not complete, or the user has
  708. #       changed the configuration file. Rather than guessing and
  709. #       chosing one of the historical md5sums, we fall through to the
  710. #       solution used if there had been no historical md5sums
  711. #       directory/file.
  712.     if [ "X$lastsum" = "X" ]; then
  713. #      b: We do not have a historical list of md5sums, or none
  714. #         matched, and we still need to initialize the
  715. #         ${old_mdsum_prefix}.old file. We can't determine whther or
  716. #         not they made any changes, so we err on the side of caution
  717. #         and ask'
  718.         if [ "X$VERBOSE" != "X" ]; then
  719.         echo >&2 "No match found, we shall ask."
  720.         fi
  721.         lastsum='AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA';
  722.     fi # the old md5sum file does not exist, and the historical
  723.        # record failed
  724.     fi # the old md5sum file does not exist (bug))
  725. else  # "$dest_file" does not exist
  726. # Step 2: If destfile does not exist, create it, set the file
  727. #         "${old_mdsum_prefix}.old" to the md5sum of the new file, and we
  728. #         are done
  729.     if [ "X$lastsum" = "X" ]; then
  730.         # Ok, so there is no indication that the package was ever
  731.         # installed on this machine.
  732.     echo >&2 ""
  733.     echo >&2 "Creating config file $dest_file with new version"
  734.     replace_conf_file;
  735.     exit 0;
  736.     elif [ "$lastsum" = "$newsum" ]; then
  737.         # OK, new version of the file is the same as the last version
  738.         # we saw. Since the user apparently has deleted the file,
  739.         # nothing needs be done, unless we have been told differently
  740.         if [ "X$force_conffmiss" != "X" ]; then
  741.             echo >&2 ""
  742.         echo >&2 "Recreating deleted config file $dest_file with new version, as asked"
  743.         replace_conf_file;
  744.         exit 0;
  745.         else
  746.             echo >&2 "Not replacing deleted config file $dest_file";
  747.         fi
  748.         
  749.     else
  750.         # OK. New upstream version. 
  751.         if [ "X$force_conffmiss" != "X" ]; then
  752.             # User has said to replace missing files, so we do so, no
  753.             # questions asked.
  754.             echo >&2 ""
  755.         echo >&2 "Recreating deleted config file $dest_file with new version, as asked"
  756.         replace_conf_file;
  757.         exit 0;
  758.         else
  759.             # Even though the user has deleted this file, they should
  760.             # be asked now, unless specified otherwise.
  761.             if [ "X$force_conffold" = "X" ]; then
  762.                 destsum='AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA';
  763.             else
  764.                 exit 0;
  765.         fi    
  766.         fi            
  767.     fi
  768. fi
  769.  
  770. # Here, the destfile exists.
  771.  
  772. # step 3: If the old md5sum and the md5sum of the new file
  773. #         do not match, we need to take action.
  774. if [ "$lastsum" = "$newsum" ]; then
  775.     if [ "X$VERBOSE" != "X" ]; then
  776.     echo >&2 "md5sums match, nothing needs be done."
  777.     fi
  778.     if [ "X$do_replace_md5sum" != "X" ]; then
  779.     replace_md5sum;
  780.     fi
  781.     exit 0;            # Hah. Match. We are done.
  782. fi
  783. #      a: If the md5sum of the dest file is the same as lastsum, replace the 
  784. #         destfile, saying we are replacing old config files
  785. if [ "$destsum" = "$lastsum" ]; then
  786.     if [ "X$force_conffold" = "X" ]; then
  787.     echo >&2 "Replacing config file $dest_file with new version"
  788.     replace_conf_file;
  789.     exit 0;
  790.     else
  791.     replace_md5sum;
  792.     cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  793.     exit 0;
  794.     fi
  795. else
  796. #      b: If the md5sum of the dest file differs from lastsum, we need to ask
  797. #         the user what action to take.
  798.     if [ "X$force_conffnew" != "X" ]; then
  799.     echo >&2 "Replacing config file $dest_file with new version"
  800.     echo >&2 "even though the files differ, since you asked for it"
  801.     replace_conf_file;
  802.     exit 0;
  803.     fi
  804.     if [ "X$force_conffold" != "X" ]; then
  805.     replace_md5sum;
  806.     cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  807.     exit 0;
  808.     fi
  809. #      c: If the destination file is the same as the new maintianer provided one,
  810. #         we need do nothing.
  811.     if [ "$newsum" = "$destsum" ]; then
  812.     if [ "X$VERBOSE" != "X" ]; then
  813.         echo >&2 "md5sums of the file in place matches, nothing needs be done."
  814.     fi
  815.     replace_md5sum;
  816.     exit 0;            # Hah. Match. We are done.
  817.     fi
  818.  
  819.  
  820.     done='NO';
  821.     while [ "X$done" = "XNO" ]; do
  822.     if [ "$DEBCONF_OK" = "YES" ] && [ "$DEBIAN_HAS_FRONTEND" ]; then
  823.         # Use debconf to prompt.
  824.         if [ "X$THREEWAY" != "X" -a -e "$statedir/cache/$cached_file" ]; then
  825.             templ=ucf/changeprompt_threeway
  826.         else
  827.             templ=ucf/changeprompt
  828.         fi
  829.         if [ "X$override_template" != "X" ]; then
  830.             choices="$(db_metaget $templ Choices-C)"
  831.             choices2="$(db_metaget $override_template Choices-C)"
  832.             if [ "$choices" = "$choices2" ]; then
  833.                 templ=$override_template
  834.             fi
  835.         fi
  836.         db_fset $templ seen false
  837.         db_reset $templ
  838.         db_subst $templ FILE "$dest_file"
  839.         db_subst $templ BASENAME $(basename "$dest_file")
  840.         db_input critical $templ || true
  841.         if ! db_go; then
  842.             # The current ucf interface does not provide a way for it
  843.             # to tell its caller that the user chose to back up.
  844.             # However, we could get here, if the caller turned on
  845.             # debconf's backup capb. The best thing to do seems to be
  846.             # to ignore requests to back up.
  847.             continue
  848.         fi
  849.         db_get $templ
  850.         ANSWER="$RET"
  851.     else
  852.         # Prompt without using debconf.
  853.         cat >&2 <<EOPRMT
  854. Configuration file \`$dest_file'
  855.  ==> File on system created by you or by a script.
  856.  ==> File also in package provided by package maintainer.
  857.    What would you like to do about it ?  Your options are:
  858.     Y or I  : install the package maintainer's version
  859.     N or O  : keep your currently-installed version
  860.       D     : show the differences between the versions
  861.       S     : show the side-by-side differences between the versions
  862. EOPRMT
  863.         if [ "X$THREEWAY" != "X" -a -e "$statedir/cache/$cached_file" ]; then
  864.             cat >&2 <<EOTD
  865.     3 or T  : show a three way difference between current, older,
  866.               and new versions of the file
  867.       M     : Do a 3 way merge between current, older,
  868.               and new versions of the file [Very Experimental]
  869. EOTD
  870.         fi
  871.         cat >&2 <<EOPEND
  872.       Z     : start a new shell to examine the situation
  873.  The default action is to keep your current version.
  874. EOPEND
  875.         if [ "X$THREEWAY" != "X" -a -e "$statedir/cache/$cached_file" ]; then
  876.             echo -n >&2 "*** " $(basename "$dest_file") \
  877.                 " (Y/I/N/O/D/3/T/M/Z) [default=N] ?"
  878.         else
  879.             echo -n >&2 "*** " $(basename "$dest_file") \
  880.                 " (Y/I/N/O/D/Z) [default=N] ?"
  881.         fi
  882.           read -e ANSWER </dev/tty
  883.     fi
  884.  
  885.     case "$ANSWER" in
  886.         install_new|y|Y|I|i)
  887.         echo >&2 "Replacing config file $dest_file with new version"
  888.         RETAIN_OLD=YES
  889.         replace_conf_file;
  890.         exit 0;
  891.         ;;
  892.         diff|D|d)
  893.         if [ -e "$dest_file" ]; then
  894.             DIFF="$(diff -uBbw "$dest_file" "$new_file")" || true
  895.         else
  896.             DIFF="$(diff -uBbw /dev/null "$new_file")" || true
  897.         fi
  898.         show_diff "$DIFF"
  899.         ;;
  900.         sdiff|S|s)
  901.         if [ -e "$dest_file" ]; then
  902.             DIFF="$( sdiff -BbW "$dest_file" "$new_file")"  || true
  903.         else
  904.             DIFF="$(sdiff -BbW /dev/null "$new_file")"  || true
  905.         fi
  906.         show_diff "$DIFF"
  907.         ;;
  908.         diff_threeway|3|t|T)
  909.         if [ -e "$statedir/cache/$cached_file" \
  910.             -a "X$THREEWAY" != "X" ]; then
  911.                     if [ -e "$dest_file" ]; then
  912.                 DIFF="$(diff3 -L Current -L Older -L New -A \
  913.                 "$dest_file" "$statedir/cache/$cached_file" \
  914.                 "$new_file")"  || true
  915.                     else
  916.                         DIFF="$(diff3 -L Current -L Older -L New -A \
  917.                 /dev/null "$statedir/cache/$cached_file" \
  918.                 "$new_file")"  || true
  919.                     fi
  920.             show_diff "$DIFF"
  921.         else 
  922.             if [ -e "$dest_file" ]; then
  923.             DIFF="$(diff -uBbw "$dest_file" "$new_file")"  || true
  924.             else
  925.             DIFF="$(diff -uBbw /dev/null "$new_file")"  || true
  926.             fi
  927.             show_diff "$DIFF"
  928.         fi
  929.         ;;
  930.         merge_threeway|M|m)
  931.         echo >&2 "Merging changes into the new version"
  932.         if [ -e "$statedir/cache/$cached_file" \
  933.             -a "X$THREEWAY" != "X" ]; then
  934.             ret=0
  935.             diff3 -L Current -L Older -L New -m \
  936.             "$dest_file" "$statedir/cache/$cached_file" \
  937.             "$new_file" > $dest_file.${NEW_SUFFIX} || ret=$?
  938.                     case "$ret" in
  939.                         0)
  940.                     new_file="$dest_file.${NEW_SUFFIX}"
  941.                     RETAIN_OLD=YES
  942.                     replace_conf_file;
  943.                             ;;
  944.                         *)
  945.                 echo >&2
  946.                     echo >&2 " Conflicts found! Please edit" \
  947.                     "\`$dest_file' and sort them out manually."
  948.                 echo >&2 " The file \`$dest_file.${NEW_SUFFIX}' has a" \
  949.                     "record of the failed merge of the configuration file."
  950.                 echo >&2
  951.                             exit 3                            
  952.                     esac
  953.         else 
  954.             replace_conf_file;
  955.         fi
  956.                 rm -f "$dest_file.${NEW_SUFFIX}" # don't need this around no mo'
  957.                 exit 0
  958.         ;;
  959.         shell|Z|z)
  960.         bash >/dev/tty </dev/tty || true
  961.         ;;
  962.         keep_current|n|N|o|O|'')
  963.         replace_md5sum;
  964.  
  965.         cp -pf "$orig_new_file" "$dest_file.${DIST_SUFFIX}"
  966.         exit 0;
  967.         ;;
  968.         *)
  969.         if [ "$DEBCONF_OK" = "YES" ]; then
  970.             echo "Error: unknown response from debconf:'$RET'" >&2
  971.             exit 1
  972.         else
  973.             echo
  974.             echo "Please answer with one of the single letters listed." >&2
  975.             echo
  976.         fi
  977.     esac
  978.     done
  979. fi
  980.  
  981. db_stop
  982.  
  983. exit 0;
  984.